package com.burst.reptile.framework.config;

import java.time.LocalDateTime;

import javax.servlet.http.HttpServletRequest;

import org.apache.ibatis.reflection.MetaObject;
import org.springframework.beans.factory.annotation.Autowired;

import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.handlers.MetaObjectHandler;
import com.burst.reptile.common.constant.Constants;
import com.burst.reptile.common.utils.SecurityUtils;
import com.burst.reptile.common.utils.ServletUtils;
import com.burst.reptile.common.utils.ToolUtil;
import com.burst.reptile.framework.redis.RedisCache;
import com.burst.reptile.framework.security.LoginUser;

import cn.hutool.core.util.StrUtil;

/**
 * mybatis-plus 自动填充
 * 
 * @author wujin
 * @date: 2020年2月21日 下午12:37:00
 */
public class MyMetaObjectHandler implements MetaObjectHandler {

	@Autowired
	private RedisCache redisCache;

	@Override
	public void insertFill(MetaObject metaObject) {

		LocalDateTime now = LocalDateTime.now();

		// 注入创建时间
		String createTimeFieldName = this.getCreateTimeFieldName();
		// 否包含该属性
		boolean hasCreateTime = metaObject.hasSetter(createTimeFieldName);
		Object createTime = getFieldValByName(createTimeFieldName, metaObject);
		if (hasCreateTime && ToolUtil.isEmpty(createTime)) {
			this.strictInsertFill(metaObject, createTimeFieldName, LocalDateTime.class, now);
		}

		// 注入创建人
		String createUserFieldName = this.getCreateUserFieldName();
		boolean hasCreateUser = metaObject.hasSetter(createUserFieldName);
		Object createUser = getFieldValByName(createUserFieldName, metaObject);
		if (hasCreateUser && ToolUtil.isEmpty(createUser)) {
			String userName = getUserName();
			if (StrUtil.isNotEmpty(userName)) {
				this.strictInsertFill(metaObject, createUserFieldName, String.class, userName);
			}
		}

		// 注入更新时间
		String updateTimeFieldName = this.getUpdateTimeFieldName();
		// 是否包含该属性
		boolean hasUpdateTime = metaObject.hasSetter(updateTimeFieldName);
		// 该值是否为空
		Object updateTime = getFieldValByName(updateTimeFieldName, metaObject);
		if (hasUpdateTime && ToolUtil.isEmpty(updateTime)) {
			this.strictUpdateFill(metaObject, updateTimeFieldName, LocalDateTime.class, now);
		}

		// 注入更新人
		String updateUserFieldName = this.getUpdateUserFieldName();
		boolean hasUpdateUser = metaObject.hasSetter(updateUserFieldName);
		Object updateUser = getFieldValByName(updateUserFieldName, metaObject);
		if (hasUpdateUser && ToolUtil.isEmpty(updateUser)) {
			String userName = getUserName();
			if (StrUtil.isNotEmpty(userName)) {
				this.strictInsertFill(metaObject, updateUserFieldName, String.class, userName);
			}
		}
	}

	@Override
	public void updateFill(MetaObject metaObject) {

		// 注入更新时间
		String updateTimeFieldName = this.getUpdateTimeFieldName();
		// 是否包含该属性
		boolean hasUpdateTime = metaObject.hasSetter(updateTimeFieldName);
		// 该值是否为空
		Object updateTime = getFieldValByName(updateTimeFieldName, metaObject);
		if (hasUpdateTime && ToolUtil.isEmpty(updateTime)) {
			this.strictUpdateFill(metaObject, updateTimeFieldName, LocalDateTime.class, LocalDateTime.now());
		}

		// 注入更新人
		String updateUserFieldName = this.getUpdateUserFieldName();
		boolean hasUpdateUser = metaObject.hasSetter(updateUserFieldName);
		Object updateUser = getFieldValByName(updateUserFieldName, metaObject);
		if (hasUpdateUser && ToolUtil.isEmpty(updateUser)) {
			String userName = getUserName();
			if (StrUtil.isNotEmpty(userName)) {
				this.strictInsertFill(metaObject, updateUserFieldName, String.class, userName);
			}
		}
	}

	/**
	 * 获取用户名
	 * @return
	 */
	protected String getUserName() {
		String userName = null;
		if (SecurityUtils.isLogin()) {
			userName = SecurityUtils.getUsername();
		}
		if (StrUtil.isEmpty(userName)) {
			HttpServletRequest request = ServletUtils.getRequest();
			String token = request.getHeader(Constants.TOKEN);
			if (StrUtil.isNotEmpty(token)) {
				Object object = redisCache.getCacheObject(Constants.LOGIN_TOKEN_KEY + token);
				if (ToolUtil.isNotEmpty(object)) {
					LoginUser loginUser = JSONObject.parseObject(JSONObject.toJSONString(object), LoginUser.class);
					userName = loginUser.getUser().getUserName();
				}
			}
		}
		return userName;
	}
	
	/**
	 * 获取创建时间字段的名称（非数据库中字段名称）
	 */
	protected String getCreateTimeFieldName() {
		return "createTime";
	}

	/**
	 * 获取创建用户字段的名称（非数据库中字段名称）
	 */
	protected String getCreateUserFieldName() {
		return "createUser";
	}

	/**
	 * 获取更新时间字段的名称（非数据库中字段名称）
	 */
	protected String getUpdateTimeFieldName() {
		return "updateTime";
	}

	/**
	 * 获取更新用户字段的名称（非数据库中字段名称）
	 */
	protected String getUpdateUserFieldName() {
		return "updateUser";
	}

}
